﻿using System;
using System.Runtime.Remoting.Messaging;
using System.Text;
using System.Data.Linq;
using System.Linq;
using GestorSQL.Utility;
using System.Threading;
using AspectIntercept;

namespace GestorSQL.DAO.InterceptDAO
{
    public class DBTraceProcessor : IPreProcessor, IPostProcessor
    {
        private string _MethodCall = string.Empty;
        private string _MethodResult = string.Empty;

        #region IPreProcessor Members

        public void Process(ref IMethodCallMessage msg)
        {
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < msg.InArgCount; i++)
                sb.AppendFormat("{0}:({1}){2}", (msg.InArgs[i] == null ? "null" : msg.InArgs[i].GetType().ToString()), (msg.InArgs[i] == null ? "null" : msg.InArgs[i].ToString()), ((i + 1) < msg.InArgCount ? "," : ""));
            _MethodCall = sb.ToString();
            msg.Properties.Add("_MethodCall", _MethodCall);
        }

        #endregion

        #region IPostProcessor Members

        public void Process(IMethodCallMessage callMsg, ref IMethodReturnMessage retMsg)
        {
            StringBuilder sb = new StringBuilder();
            bool fail = false;
            Exception e = retMsg.Exception;
            if (e != null)
            {
                fail = true;
                sb.Append(e.ToString());
            }
            else
            {
                for (int i = 0; i < retMsg.OutArgCount; i++)
                    sb.AppendFormat("{0}:({1}){2}", (retMsg.OutArgs[i] == null ? "null" : retMsg.OutArgs[i].GetType().ToString()), (retMsg.OutArgs[i] == null ? "null" : retMsg.OutArgs[i].ToString()), ((i + 1) < retMsg.OutArgCount ? "," : ""));
            }
            _MethodResult = sb.ToString();
            _MethodCall = callMsg.Properties["_MethodCall"].ToString();

            using (BitacoraEntitiesDataContext dc = new BitacoraEntitiesDataContext("BitacoraConnectionString".GetFromConnStrings()))
            {
                dc.Bitacoras.InsertOnSubmit(new Bitacora()
                    {
                        Fecha = dc.ExecuteQuery<DateTime>("select getdate()").Single(),
                        Fallo = fail,
                        Ip = Miscellanious.GetRemoteIP(),
                        Argumentos = _MethodCall,
                        Metodo = callMsg.MethodName,
                        Retorno = _MethodResult,
                        Usuario = Thread.CurrentPrincipal.Identity.Name
                    });
                dc.SubmitChanges();
            }
        }

        #endregion
    }
}
